import { Injectable } from '@angular/core';
import { environment } from '../../environments/environment';
import { HttpClient, HttpHeaders, HttpParams, HttpResponse } from '@angular/common/http';
import { catchError, map } from 'rxjs/operators';
import { MemberVo } from '../model/member-vo';
import { MemberProfileVo } from '../model/member-profile-vo';
import { MemberRecordVo } from '../model/member-record-vo';
import { throwError, of, Observable } from 'rxjs';
import { MemberSocialVo } from '../model/member-social-vo';
import { EntityPageResult } from '../model/entity-page-result';
import { ThreadsRecordVo } from '../model/threads-record-vo';
@Injectable({
  providedIn: 'root'
})
export class MemberService {
  private restRequestURI: string = environment.restURI + '/member';
  //是否开启了邀请码:全局设置
  public activeInvite: boolean = environment.registeInvite;
  /**
   * 会员REST API服务
   */
  constructor(private http: HttpClient) { }
  /**
   * 查看会员的头像
   * @param uid 会员ID
   * @returns 成功时返回200(响应的内容中包含解码后的地址),失败时返回404(无具体错误描述)
   */
  public getAvatar(uid: number): Observable<string> {
    if (0 >= uid) {
      return of('assets/avatar/empty.png');
      //throwError('会员ID非可用值'); 
    }
    return this.http.get(this.restRequestURI + '/' + uid + '/avatar', { responseType: 'text' })
      .pipe(map((e: string) => 'assets/avatar' + e))
      .pipe(catchError(err => of('assets/avatar/empty.png')));
  }
  /**
   * 查看指定的会员
   * @param uid 会员ID
   */
  public get(uid: number): Observable<MemberVo> {
    if (0 >= uid) {
      return throwError('会员ID非可用值');
    }
    return this.http.get<MemberVo>(this.restRequestURI + '/' + uid);
  }
  /**
   * 查看指定会员的个人信息,包含会员等级信息
   * @param uid 会员ID
   * @returns 若会员不存在会返回一个游客实例
   */
  public getProfile(uid: number): Observable<MemberProfileVo> {
    if (0 >= uid) {
      return throwError('会员ID非可用值');
    }
    //:/{id}/profile
    return this.http.get<MemberProfileVo>(this.restRequestURI + '/' + uid + '/profile');
  }
  /**
   * 注册新会员
   * @param memberNames 会员的登录帐号
   * @param memberPswd 会员的登录密码/未加密的值
   * @param memberNickname 会员的昵称
   * @param inviteCode 注册的邀请码,未开启邀请码注册时使用使用空字符串
   * @param token 
   * @param ipAddr 
   * @returns 成功的状态码是200(返回一个MemberVo实例),失败的状态是400(响应的内容中包含错误消息)
   */
  public signUp(memberNames: string, memberPswd: string, memberNickname: string, inviteCode: string, token: string, ipAddr: string): Observable<MemberVo> {
    if (!memberNames || !memberPswd) {
      return throwError('会员登录帐号或密码非可用值');
    }
    if (this.activeInvite && (!inviteCode || inviteCode.length < 6)) {
      return throwError('注册邀请码非可用值');
    }
    //:/registe
    const httpOptions = {
      headers: {
        'Content-Type': 'application/x-www-form-urlencoded'
      }
    };
    let body = new HttpParams().set('names', memberNames).set('password', memberPswd).set('invite', inviteCode).set('token', token).set('ip', ipAddr);
    if (memberNickname && memberNickname.length >= 5) {
      body = body.set('nickname', memberNickname);
    }
    console.log('register body:'+body.toString());
    return this.http.post<MemberVo>(this.restRequestURI + '/registe', body.toString(), httpOptions);
  }
  /**
   * 登录
   * @param memberNames 会员的登录帐号
   * @param memberPswd 会员的登录密码/未加密的值
   * @param token 
   * @param ipAddr 
   * @returns 成功的状态码是200(返回一个MemberVo实例),失败的状态是404(表示会员不存在,响应中没有错误消息)
   */
  public signIn(memberNames: string, memberPswd: string, token: string, ipAddr: string): Observable<MemberVo> {
    if (!memberNames || !memberPswd) {
      return throwError('会员登录帐号或密码非可用值');
    }
    //:/checkIn
    const httpOptions = {
      headers: {
        'Content-Type': 'application/x-www-form-urlencoded'
      }
    };
    const body = new HttpParams().set('names', memberNames).set('password', memberPswd).set('token', token).set('ip', ipAddr);
    return this.http.post<MemberVo>(this.restRequestURI + '/checkIn', body.toString(), httpOptions);
  }
  /**
   * 注销/退出
   * @param uid 会员ID
   * @param memberNames 会员的登录帐号
   * @param token 
   * @param ipAddr 
   * @returns 成功的状态码是200,失败的状态是417
   */
  public logout(uid: number, memberNames: string, token: string, ipAddr: string): Observable<HttpResponse<string>> {
    if (0 >= uid) {
      return throwError('会员ID非可用值');
    }
    if (!memberNames) {
      return throwError('会员登录帐号非可用值');
    }
    //:/checkOut
    const httpOptions = {
      headers: {
        'Content-Type': 'application/x-www-form-urlencoded'
      }
    };
    const body = new HttpParams().set('id', uid + '').set('names', memberNames).set('token', token).set('ip', ipAddr);
    return this.http.post<HttpResponse<string>>(this.restRequestURI + '/checkOut', body.toString(), httpOptions);//状态码
  }
  /**
   * 查看指定会员最后一条登录记录
   * @param uid 会员ID
   * @param memberNames 会员的登录帐号
   */
  public getLoginLastRecord(uid: number, memberNames: string): Observable<MemberRecordVo> {
    if (0 >= uid) {
      return throwError('会员ID非可用值');
    }
    if (!memberNames) {
      return throwError('会员登录帐号非可用值');
    }
    //:/login/lastrecord/{id}/{names}
    return this.http.get<MemberRecordVo>(this.restRequestURI + '/login/lastrecord/' + uid + '/' + memberNames);
  }
  /**
   * 找回密码的第一步
   * @param memberNames 会员的登录帐号
   * @param memberSocialEmail 会员社会化信息中的填写的邮箱
   * @returns 成功的状态码是200,失败的状态是404
   */
  public querySocial(memberNames: string, memberSocialEmail: string): Observable<MemberSocialVo> {
    if (!memberNames) {
      return throwError('会员登录帐号非可用值');
    }
    if (!memberSocialEmail) {
      return throwError('会员绑定的邮箱非可用值');
    }
    const httpOptions = {
      headers: {
        'Content-Type': 'application/x-www-form-urlencoded'
      }
    };
    //:/social/query
    const body = new HttpParams().set('names', memberNames).set('mail', memberSocialEmail);
    return this.http.post<MemberSocialVo>(this.restRequestURI + '/social/query', body.toString(), httpOptions);
  }
  /**
   * 查看指定会员的社会化信息
   * @param uid 会员ID
   * @returns 成功的状态码是200,失败的状态是404
   */
  public getSocial(uid: number): Observable<MemberSocialVo> {
    if (0 >= uid) {
      return throwError('会员ID非可用值');
    }
    //:/{id}/social
    return this.http.get<MemberSocialVo>(this.restRequestURI + '/' + uid + '/social');
  }
  /**
   * 创建会员的社会化信息
   * @param uid 会员ID
   * @param memberNames 会员登录帐号
   * @param weibo 微博帐号
   * @param weixin 微信号
   * @param qq qq号码
   * @param mail 邮箱地址
   * @param token 
   * @param ipAddr 
   * @returns 成功的状态码是200,失败的状态是404
   */
  public createSocial(uid: number, memberNames: string, weibo: string, weixin: string, qq: string, mail: string, token: string, ipAddr: string): Observable<MemberSocialVo> {
    if (0 >= uid) {
      return throwError('会员ID非可用值');
    }
    if (!memberNames) {
      return throwError('会员登录帐号非可用值');
    }
    const httpOptions = {
      headers: {
        'Content-Type': 'application/x-www-form-urlencoded'
      }
    };
    //:/{id}/social/create
    const body = new HttpParams().set('names', memberNames).set('weibo', weibo).set('weixin', weixin).set('qq', qq).set('mail', mail).set('token', token).set('ip', ipAddr);
    return this.http.post<MemberSocialVo>(this.restRequestURI + '/' + uid + '/social/create', body.toString(), httpOptions);
  }
  /**
   * 更新会员的社会化信息
   * @param uid 会员ID
   * @param memberNames 会员登录帐号
   * @param socialId 社会化信息ID
   * @param weibo 微博帐号
   * @param weixin 微信号
   * @param qq qq号码
   * @param mail 邮箱地址
   * @param token 
   * @param ipAddr 
   * @returns 成功的状态码是200,失败的状态是417
   */
  public editSocial(uid: number, memberNames: string, socialId: number, weibo: string, weixin: string, qq: string, mail: string, token: string, ipAddr: string): Observable<HttpResponse<string>> {
    if (0 >= uid) {
      return throwError('会员ID非可用值');
    }
    if (!memberNames) {
      return throwError('会员登录帐号非可用值');
    }
    if (0 >= socialId) {
      return throwError('社会化信息缺失');
    }
    const httpOptions = {
      headers: {
        'Content-Type': 'application/x-www-form-urlencoded'
      }
    };
    //:/{id}/social/modify
    const body = new HttpParams().set('names', memberNames).set('record', socialId + '').set('weibo', weibo).set('weixin', weixin).set('qq', qq).set('mail', mail).set('token', token).set('ip', ipAddr);
    return this.http.put<HttpResponse<string>>(this.restRequestURI + '/' + uid + '/social/modify', body.toString(), httpOptions);//状态码
  }
  /**
   * 找回密码的第二步
   * @param uid 会员ID
   * @param newPswd 会员新密码
   * @param token 
   * @param ipAddr 
   * @returns 成功的状态码是200,失败的状态是417
   */
  public resetAnonyPassword(uid: number, newPswd: string, token: string, ipAddr: string): Observable<HttpResponse<string>> {
    if (0 >= uid) {
      return throwError('会员ID非可用值');
    }
    if (!newPswd || newPswd.length < 6) {
      return throwError('新密码非可用值');
    }
    const httpOptions = {
      headers: {
        'Content-Type': 'application/x-www-form-urlencoded'
      }
    };
    //:/{member}/password/reset
    const body = new HttpParams().set('current', newPswd).set('token', token).set('ip', ipAddr);
    return this.http.put<HttpResponse<string>>(this.restRequestURI + '/' + uid + '/password/reset', body.toString(), httpOptions);//状态码
  }

  /**
   * 更新会员的个性签名
   * @param uid 会员ID
   * @param signature 个性签名
   * @param memberNickname 会员昵称
   * @param token 
   * @param ipAddr 
   * @returns 成功的状态码是200,失败的状态是417
   */
  public editProfile(uid: number, signature: string, memberNickname: string, token: string, ipAddr: string): Observable<HttpResponse<string>> {
    if (0 >= uid) {
      return throwError('会员ID非可用值');
    }
    if (!memberNickname || memberNickname.length < 5) {
      return throwError('会员昵称非可用值');
    }
    const httpOptions = {
      headers: {
        'Content-Type': 'application/x-www-form-urlencoded'
      }
    };
    //:/{id}/profile/modify
    const body = new HttpParams().set('signature', signature).set('nickname', memberNickname).set('token', token).set('ip', ipAddr);
    return this.http.put<HttpResponse<string>>(this.restRequestURI + '/' + uid + '/profile/modify', body.toString(), httpOptions);//状态码
  }
  /**
   * 更新会员的登录密码
   * @param uid 会员ID
   * @param originalPswd 当前使用的密码/旧的
   * @param currentPswd 新的密码
   * @param token 
   * @param ipAddr 
   * @returns 成功的状态码是200,失败的状态是417
   */
  public editPassword(uid: number, originalPswd: string, currentPswd: string, token: string, ipAddr: string): Observable<HttpResponse<string>> {
    if (0 >= uid) {
      return throwError('会员ID非可用值');
    }
    if (!originalPswd) {
      return throwError('当前密码非可用值');
    }
    if (!currentPswd) {
      return throwError('前密码非可用值');
    }
    const httpOptions = {
      headers: {
        'Content-Type': 'application/x-www-form-urlencoded'
      }
    };
    //:/{id}/password/modify
    const body = new HttpParams().set('original', originalPswd).set('current', currentPswd).set('token', token).set('ip', ipAddr);
    return this.http.put<HttpResponse<string>>(this.restRequestURI + '/' + uid + '/password/modify', body.toString(), httpOptions);//状态码
  }
  /**
   * 更新会员的头像
   * 
   * @param uid 会员ID
   * @param avatarPath 会员头像/未编码的,格式:/风格/头像的文件名,例:/default/1.jpeg
   * @param appLocalDomain 项目的域名,例:http://app.test.com
   * @param avatarDefaultDirect 头像存储的目录名,默认为:avatar
   * @param token 
   * @param ipAddr 
   * @returns 成功的状态码是200(响应内容是编码后的头像地址),失败的状态是404
   */
  public editAvatar(uid: number, avatarPath: string, appLocalDomain: string = 'http://app.test.com', avatarDefaultDirect: string = 'avatar', token: string, ipAddr: string): Observable<string> {
    if (0 >= uid) {
      return throwError('会员ID非可用值');
    }
    if (!avatarPath) {
      return throwError('头像非可用值');
    }
    //:/{id}/avatar/modify
    //avatar=%2Fdefault%2F9.jpeg&app_domain=http%3A%2F%2Fcenter.test.com&app_avatar_direct=avatar&token=zmyKnIkg&ip=127.0.0.1
    const headers = new HttpHeaders().set('Content-Type', 'application/x-www-form-urlencoded; charset=utf-8');
    const body = new HttpParams().set('avatar', avatarPath).set('app_domain', appLocalDomain).set('app_avatar_direct', avatarDefaultDirect).set('token', token).set('ip', ipAddr);
    return this.http.put(this.restRequestURI + '/' + uid + '/avatar/modify', body.toString(), { headers, "responseType": "text" });
  }
  /**
   * 查看指定会员的活跃记录
   * @param uid 会员ID
   * @param page 
   * @param pageSize 
   */
  public getActionHistory(uid: number, page: number = 1, pageSize: number = 20): Observable<EntityPageResult<ThreadsRecordVo>> {
    if (0 >= uid) {
      return throwError('会员ID非可用值');
    }
    //:/{id}/history/{page}/{number}
    return this.http.get<EntityPageResult<ThreadsRecordVo>>(this.restRequestURI + '/' + uid + '/history/' + page + '/' + pageSize);
  }
  /**
   * 查看指定会员的收藏记录
   * @param uid 会员ID
   * @param page 
   * @param pageSize 
   */
  public getFavoriteTopic(uid: number, page: number = 1, pageSize: number = 20): Observable<EntityPageResult<ThreadsRecordVo>> {
    if (0 >= uid) {
      return throwError('会员ID非可用值');
    }
    //:/{id}/topic/favorite/{page}/{number}
    return this.http.get<EntityPageResult<ThreadsRecordVo>>(this.restRequestURI + '/' + uid + '/topic/favorite/' + page + '/' + pageSize);
  }
  /**
   * 查看指定会员的点赞记录
   * @param uid 会员ID
   * @param page 
   * @param pageSize 
   */
  public getLikeTopic(uid: number, page: number = 1, pageSize: number = 20): Observable<EntityPageResult<ThreadsRecordVo>> {
    if (0 >= uid) {
      return throwError('会员ID非可用值');
    }
    //:/{id}/topic/like/{page}/{number}
    return this.http.get<EntityPageResult<ThreadsRecordVo>>(this.restRequestURI + '/' + uid + '/topic/like/' + page + '/' + pageSize);
  }
  /**
   * 检测会员的登录帐号是否已经存在
   * @param names 登录帐号
   * @returns 200表示可以使用,417表示不可用(响应的内容中有具体的错误消息)
   */
  public isExistsNames(names: string): Observable<string> {
    //:/detection/{names}
    if (!names) {
      return throwError('会员登录帐号不可用');
    }
    const headers = new HttpHeaders().set('Content-Type', 'text/plain; charset=utf-8');
    return this.http.get(this.restRequestURI + '/detection/' + names, { headers, responseType: 'text' });
  }
}
